﻿using Dapper.Sharding;
using FastApi;
using Microsoft.Owin;
using Microsoft.Owin.Cors;
using Microsoft.Owin.FileSystems;
using Microsoft.Owin.StaticFiles;
using Newtonsoft.Json;
using Owin;
using System;
using System.Runtime.Remoting.Contexts;
using System.Web.Http;
using Test.Module;

namespace Test
{
    public class Startup
    {
        public void Configuration(IAppBuilder app)
        {

#if DEBUG
            app.UseErrorPage();
#endif
            app.UseCors(CorsOptions.AllowAll);

            #region Cors Domain

            //var policy = new CorsPolicy()
            //{
            //    AllowAnyHeader = true,
            //    AllowAnyMethod = true,
            //    SupportsCredentials = true
            //};

            //// list of domains that are allowed can be added here
            //policy.Origins.Add("domain");
            ////be sure to include the port:
            ////example: "http://localhost:8081"

            //app.UseCors(new CorsOptions
            //{
            //    PolicyProvider = new CorsPolicyProvider
            //    {
            //        PolicyResolver = context => Task.FromResult(policy)
            //    }
            //});

            #endregion

            var fastApp = new FastApp(app);
            fastApp.LogTime = true;

            fastApp.AddParams(typeof(DistributedTransaction), new FastParamCreator
            {
                Create = ctx =>
                {
                    return new DistributedTransaction();
                },
                Dispose = (ctx, obj) =>
                {
                    var tran = (DistributedTransaction)obj;
                    tran.Dispose();
                },
                Commit = (ctx, obj) =>
                {
                    var tran = (DistributedTransaction)obj;
                    tran.CommitAsync();
                },
                Rollback = (ctx, obj) =>
                {
                    var tran = (DistributedTransaction)obj;
                    tran.Rollback();
                }
            });

            fastApp.AddRoute(typeof(TestModule).Assembly);


            fastApp.OnBeforeResponse = async fastCtx =>
            {
                var json = JsonConvert.SerializeObject(new { code = 0, data = fastCtx.ResponseData });
                await fastCtx.HttpContext.Response.WriteAsync(json);
            };
            fastApp.OnException += async (fastCtx, ex) =>
            {
                var json = JsonConvert.SerializeObject(new { code = 0, msg = ex.Message });
                await fastCtx.HttpContext.Response.WriteAsync(json);
            };
            fastApp.OnAfterResponse += fastCtx =>
            {
                Console.WriteLine($"方法：{fastCtx.ExecuteTime}ms 序列化:{fastCtx.JsonSerialTime}ms");
            };

            Console.WriteLine("IsDevelopment==>" + fastApp.IsDevelopment);
            Console.WriteLine("IsProduction==>" + fastApp.IsProduction);
            Console.WriteLine(fastApp.BaseDirectory);
            Console.WriteLine(fastApp.ContentRootPath);
            Console.WriteLine(fastApp.WebRootPath);

            //WebApi
            var config = GetWebApiConfig();
            app.UseWebApi(config);

            //wwwroot
            var fileOptions = new FileServerOptions()
            {
                RequestPath = PathString.Empty,
                EnableDefaultFiles = true,
                EnableDirectoryBrowsing = false,
                //FileSystem = new PhysicalFileSystem(@".\wwwroot"),
                FileSystem = new PhysicalFileSystem(fastApp.WebRootPath),
            };
            fileOptions.StaticFileOptions.ServeUnknownFileTypes = true;
            app.UseFileServer(fileOptions);

            //app.UseWelcomePage();
        }

        private HttpConfiguration GetWebApiConfig()
        {
            HttpConfiguration config = new HttpConfiguration();

            config.MapHttpAttributeRoutes();

            config.Routes.MapHttpRoute(
            name: "Default",
            routeTemplate: "api/{controller}/{action}",
            defaults: new { id = RouteParameter.Optional }
            );

            //config.Formatters.JsonFormatter.MediaTypeMappings.Add(new QueryStringMapping("datatype", "json", "application/json"));

            config.Formatters.Remove(config.Formatters.XmlFormatter);

            config.Formatters.JsonFormatter.SerializerSettings = new Newtonsoft.Json.JsonSerializerSettings()
            {
                NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore
            };

            return config;
        }

    }
}
